/*
* Copyright 2011 Pavel Kozhin 
*
* Licensed under the Apache License, Version 2.0 (the "License"); 
* you may not use this file except in compliance with the License. 
* You may obtain a copy of the License at 
* 
* http://www.apache.org/licenses/LICENSE-2.0
* 
* Unless required by applicable law or agreed to in writing, software 
* distributed  under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
* See the License for the specific language governing permissions and 
* limitations under the License.
*
* Author: Pavel Kozhin.
*/
package org.etherframework.mediation.core
{
	import org.etherframework.IEther;
	import org.etherframework.common.mediation.IMediationProvider;
	import org.etherframework.core.common.IInstanceFactory;
	import org.etherframework.core.utils.ClassUtils;
	import org.etherframework.mediation.manager.IMediationManager;
	import org.floxy.IProxyRepository;

	[ExcludeClass]
	public final class MediationFactory implements IInstanceFactory
	{
		private var _owner:IMediationManager;
		private var _repository:IProxyRepository;
		
		public function MediationFactory(owner:IMediationManager, 
										 repository:IProxyRepository)
		{
			if (!owner)
				throw new ArgumentError("Argument owner:MediationManager can not be null.");
			
			_repository = repository;
			_owner = owner;
		}
		
		public function createInstance(generator:Class, args:Array, ether:IEther):Object
		{
			var result:Object;
			var provider:org.etherframework.mediation.core.Provider;
			
			// trace("MediationFactory.createInstance(): " + getQualifiedClassName(generator));
			
			if (_repository && _owner.hasMediation(generator))
			{
				provider = _owner.createProvider(ether);
				result = _repository.create(generator, args, provider);
				return result;
			}
			
			result = ClassUtils.instantiate(generator, args);
			
			if ((result is org.etherframework.common.mediation.IMediationProvider) && _repository)
				throw new Error("Class "+ generator + " is marked as IMediationProvider " +
					"but was not processed by org.etherframework.core.manager::IMediationManager. " +
					"Make sure that you processed this class before instantiation e.g. " +
					"by subclassing and using EtherPreloader.");
			
			return result;
		}
	}
}